package configs

import (
	"fmt"
	"gin-lite/internal/pkg/env"
	"gin-lite/internal/pkg/utils/file"
	"github.com/spf13/viper"
	"os"
)

var config = new(Config)

type Config struct {
	Server Server
	Log    Log
	Mysql  map[string]DbItem
	Redis  Redis
}

type Server struct {
	Name string
	Port string
}

type Log struct {
	Level  string
	Output struct {
		Console struct {
			Enable bool
		}
		File struct {
			Path       string
			MaxSize    int `mapstructure:"max_size"`
			MaxBackups int `mapstructure:"max_backups"`
			MaxAge     int `mapstructure:"max_age"`
			Compress   bool
		}
	}
}

type DbItem struct {
	Log struct {
		Enable bool
		Level  string
		Format string
		Type   string
		Path   string
	}
	Write struct {
		EnableSql    bool `mapstructure:"enable_sql"`
		Host         string
		Port         int
		Database     string
		Username     string
		Password     string
		Charset      string
		Timeout      int
		WriteTimeOut int `mapstructure:"write_time_out"`
		ReadTimeOut  int `mapstructure:"read_time_out"`
		MaxIdleConns int `mapstructure:"max_idle_conns"`
		MaxOpenConns int `mapstructure:"max_open_conns"`
	}
	Read struct {
		EnableSql    bool `mapstructure:"enable_sql"`
		Host         string
		Port         int
		Database     string
		Username     string
		Password     string
		Charset      string
		Timeout      int
		WriteTimeOut int `mapstructure:"write_time_out"`
		ReadTimeOut  int `mapstructure:"read_time_out"`
		MaxIdleConns int `mapstructure:"max_idle_conns"`
		MaxOpenConns int `mapstructure:"max_open_conns"`
	}
}

type Redis struct {
	Addr           string
	Port           string
	Username       string
	Password       string
	Db             int
	PoolSize       int `mapstructure:"pool_size"`
	MaxActiveConns int `mapstructure:"max_active_conns"`
}

func init() {
	var configFile string

	workDir, _ := os.Getwd()

	switch env.Active().Value() {
	case "dev":
		configFile = fmt.Sprintf("%s/configs/dev_configs.yaml", workDir)
	case "fat":
		configFile = fmt.Sprintf("%s/configs/fat_configs.yaml", workDir)
	case "uat":
		configFile = fmt.Sprintf("%s/configs/uat_configs.yaml", workDir)
	case "pro":
		configFile = fmt.Sprintf("%s/configs/pro_configs.yaml", workDir)
	default:
		configFile = fmt.Sprintf("%s/configs/fat_configs.yaml", workDir)
	}

	if !file.IsFileExist(configFile) {
		panic("Error: config is not exist. load file is " + configFile)
	}

	viper.SetConfigFile(configFile)
	viper.SetConfigType("yaml")

	err := viper.ReadInConfig()
	if err != nil {
		panic(err)
	}

	err = viper.Unmarshal(config)
	if err != nil {
		panic(err)
	}
}

func Get() *Config {
	return config
}
